package system

import (
	"errors"
	"ltbz/cultural_tourism_api/models/system"
	"ltbz/cultural_tourism_api/utils"
	"time"
)

func AddRole(req *system.SysRoleAddReq) (err error, errMsg string) {
	role := new(system.SysRole)
	// 判断角色名称是否已存在
	roleItem, err := role.GetRoleByRoleName(req.RoleName)
	if err != nil && err.Error() != utils.ErrNoRow() {
		return
	}
	if roleItem != nil && roleItem.RoleId > 0 {
		err = errors.New("角色名称已经存在")
		errMsg = "角色名称已存在"
		return
	}
	// 添加角色
	role.RoleName = req.RoleName
	role.CreateTime = time.Now()
	role.ModifyTime = time.Now()
	_, err = role.Add()
	if err != nil {
		errMsg = "添加角色出错"
		err = errors.New(errMsg + "Err:" + err.Error())
		return
	}
	return
}

func EditRoleMenu(req *system.SysRoleMenuEditReq) (err error, errMsg string) {
	role := new(system.SysRole)
	// 判断角色名称是否已存在
	_, err = role.GetRoleByRoleId(req.RoleId)
	if err != nil {
		if err.Error() == utils.ErrNoRow() {
			errMsg = "角色不存在或者已经被删除"
			err = errors.New(errMsg + "Err:" + err.Error())
			return
		}
		errMsg = "查询角色出错"
		err = errors.New(errMsg + "Err:" + err.Error())
		return
	}
	//删除绑定的所有菜单
	roleMenu := new(system.SysRoleMenu)
	cond := "role_id = ?"
	pars := make([]interface{}, 0)
	pars = append(pars, req.RoleId)
	err = roleMenu.DeleteByCondition(cond, pars)
	if err != nil {
		errMsg = "删除角色原先绑定的菜单出错"
		err = errors.New(errMsg + "Err:" + err.Error())
		return
	}
	//给角色添加菜单权限
	list := make([]*system.SysRoleMenu, 0)
	if len(req.MenuIdList) > 0 {
		for _, v := range req.MenuIdList {
			item := new(system.SysRoleMenu)
			item.RoleId = req.RoleId
			item.MenuId = v
			item.CreateTime = time.Now()
			item.ModifyTime = time.Now()
			list = append(list, item)
		}
		if err = roleMenu.AddMulti(list); err != nil {
			errMsg = "给角色添加菜单权限出错"
			err = errors.New(errMsg + "Err:" + err.Error())
			return
		}
	}
	return
}

func RoleMenuList(req *system.SysRoleMenuListReq) (ret system.SysRoleMenuResp, err error, errMsg string) {
	//查询角色绑定的菜单
	roleMenu := new(system.SysRoleMenu)
	cond := " AND rm.role_id = ?"
	pars := make([]interface{}, 0)
	pars = append(pars, req.RoleId)
	roleHasMenuList, err := roleMenu.GetMenuListByCondition(cond, pars)
	if err != nil {
		errMsg = "查询角色绑定的菜单出错"
		err = errors.New(errMsg + "Err:" + err.Error())
		return
	}
	RoleMenuMap := make(map[int64]struct{}, 0)
	HasMenuIds := make([]int64, 0)
	for _, v := range roleHasMenuList {
		RoleMenuMap[v.MenuId] = struct{}{}
		HasMenuIds = append(HasMenuIds, v.MenuId)
	}
	//查询所有菜单列表
	menu := new(system.SysMenu)
	orderStr := " sort ASC, create_time, menu_id DESC"
	childList, err := menu.GetMenuListByCondition("", []interface{}{}, orderStr)
	if err != nil {
		return
	}
	list := make([]*system.MenuListItemResp, 0)
	for _, v := range childList {
		tmp := &system.MenuListItemResp{
			MenuId:       v.MenuId,
			ParentId:     v.ParentId,
			Name:         v.Name,
			Sort:         v.Sort,
			Path:         v.Path,
			PathName:     v.PathName,
			IconPath:     v.IconPath,
			Component:    v.Component,
			Hidden:       v.Hidden,
			HiddenLayout: v.HiddenLayout,
			Level:        v.Level,
			MenuType:     v.MenuType,
			ButtonCode:   v.ButtonCode,
			CreateTime:   v.CreateTime.Format(utils.FormatDateTime),
			ModifyTime:   v.ModifyTime.Format(utils.FormatDateTime),
			Children:     nil,
		}
		if _, ok := RoleMenuMap[tmp.MenuId]; ok {
			tmp.HasBind = true
		}
		list = append(list, tmp)
	}
	//组装返回值
	list = getMenuTreeRecursive(list, 0)
	ret.List = list
	ret.ChoiceList = HasMenuIds
	return
}

func DeleteRole(req *system.SysRoleDelReq) (err error, errMsg string) {
	role := new(system.SysRole)
	// 判断角色名称是否已存在
	_, err = role.GetRoleByRoleId(req.RoleId)
	if err != nil {
		if err.Error() == utils.ErrNoRow() {
			errMsg = "角色不存在或者已经被删除"
			err = errors.New(errMsg + "Err:" + err.Error())
			return
		}
		errMsg = "查询角色出错"
		err = errors.New(errMsg + "Err:" + err.Error())
		return
	}
	//删除绑定的所有菜单
	roleMenu := new(system.SysRoleMenu)
	cond := " role_id = ?"
	pars := make([]interface{}, 0)
	pars = append(pars, req.RoleId)
	err = roleMenu.DeleteByCondition(cond, pars)
	if err != nil {
		errMsg = "删除角色原先绑定的菜单出错"
		err = errors.New(errMsg + "Err:" + err.Error())
		return
	}
	//查询与角色绑定的所有账号
	sysUser := new(system.SysUser)
	aCond := " AND role_id = ?"
	aPars := make([]interface{}, 0)
	aPars = append(aPars, req.RoleId)

	admins, err := sysUser.GetAdminListByCondition(aCond, aPars)
	if err != nil {
		errMsg = "查询角色对应的用户出错"
		err = errors.New(errMsg + "Err:" + err.Error())
		return
	}
	if len(admins) > 0 {
		errMsg = "有账号绑定该角色，不可删除"
		err = errors.New(errMsg)
		return
	}
	// 删除角色
	role.RoleId = req.RoleId
	err = role.Delete()
	if err != nil {
		errMsg = "删除角色出错"
		err = errors.New(errMsg + "Err:" + err.Error())
		return
	}
	return
}
